package ru.susu.algebra.matrix;

import java.util.ArrayList;
import java.util.Arrays;
import java.util.List;

/**
 * @author akargapolov
 * @since: 09.03.2009
 */
public class Matrix
{
	private Object[][] _data;
	private int _rows;
	private int _cols;

	public Matrix(int rows, int cols)
	{
		_data = new Object[rows][cols];
		_rows = rows;
		_cols = cols;
	}

	public Object getValue(int row, int col)
	{
		return _data[row][col];
	}

	public void setValue(int row, int col, Object value)
	{
		_data[row][col] = value;
	}

	public int getRows()
	{
		return _rows;
	}

	public int getCols()
	{
		return _cols;
	}

	/**
	 * Возвращает строку в виде массива
	 * @param row номер требуемой строки
	 * @return строка в виде массива
	 */
	public Object[] getArrayRow(int row)
	{
		return _data[row];
	}

	/**
	 * Возвращает одну строку матрицы в виде {@link List}}
	 * @param row индекс строки
	 * @return строка матрицы
	 */
	public List<Object> getRow(int row)
	{
		List<Object> result = new ArrayList<Object>(_cols);
		for (int col = 0; col < _cols; col++)
		{
			result.add(_data[row][col]);
		}
		return result;
	}

	/**
	 * Добавление строки в матрицу. Количество элементов новой строки и количество столбцов матрицы должны совпадать.
	 * @param list новая строка матрицы в виде {@link List}
	 */
	public void addRow(List<Object> list)
	{
		if (list.size() != _cols)
		{
			throw new RuntimeException("Add row error. Different lengths.");
		}
		_rows++;
		_data = Arrays.copyOf(_data, _rows);
		_data[_rows - 1] = list.toArray(new Object[_cols]);
	}

	/**
	 * Добавление столбца в матрицу. Количество элементов нового столбца и количество строк матрицы должны совпадать.
	 * @param list новый столбец
	 * @param index индекс нового столбца
	 */
	public void addColumn(List<Object> list, int index)
	{
		if (list.size() != _rows)
		{
			throw new RuntimeException("Add column error. Different lengths.");
		}
		_cols++;
		for (int row = 0; row < _rows; row++)
		{
			_data[row] = Arrays.copyOf(_data[row], _cols);
			for (int col = _cols - 1; col > index; col--)
			{
				_data[row][col] = _data[row][col - 1];
			}
			_data[row][index] = list.get(row);
		}
	}

	@Override
	public String toString()
	{
		StringBuffer buffer = new StringBuffer();
		for (int row = 0;row<_rows;row++)
		{
			buffer.append(Arrays.toString(_data[row])).append("\n");
		}
		return buffer.toString();
	}

}
